package de.mmis.core.pojop.answer;

import java.io.ByteArrayOutputStream;
import java.io.IOException;
import java.io.OutputStream;

import org.apache.log4j.Logger;

import de.mmis.core.base.Toolbox;

public class HTTPAnswer implements Answer {

	private final static Logger LOGGER = Logger.getLogger(HTTPAnswer.class);

	public final static String DEFAULT_PROTOCOL_TYPE = "HTTP/1.1";
	public final static String DEFAULT_CONTENT_TYPE = "text/plain; charset=utf-8";
	public final static String DEFAULT_STATUS = "200 OK";
	public final static boolean DEFAULT_KEEPALIVE = false;

	private byte[] content;

	private boolean writeHeader;

	private String contentType;
	private boolean keepAlive;
	private String status;
	private String protocolType;

	public HTTPAnswer(byte[] content, boolean writeHeader) {
		this(content, DEFAULT_CONTENT_TYPE, DEFAULT_KEEPALIVE, DEFAULT_STATUS,
				DEFAULT_PROTOCOL_TYPE);
		this.writeHeader = writeHeader;
	}

	public HTTPAnswer(byte[] content) {
		this(content, DEFAULT_CONTENT_TYPE, DEFAULT_KEEPALIVE, DEFAULT_STATUS,
				DEFAULT_PROTOCOL_TYPE);
	}

	public HTTPAnswer(byte[] content, String contentType) {
		this(content, contentType, DEFAULT_KEEPALIVE, DEFAULT_STATUS,
				DEFAULT_PROTOCOL_TYPE);
	}

	public HTTPAnswer(byte[] content, String contentType, boolean keepAlive) {
		this(content, contentType, keepAlive, DEFAULT_STATUS,
				DEFAULT_PROTOCOL_TYPE);
	}

	public HTTPAnswer(byte[] content, String contentType, boolean keepAlive,
			String status) {
		this(content, contentType, keepAlive, status, DEFAULT_PROTOCOL_TYPE);
	}

	public HTTPAnswer(byte[] content, String contentType, boolean keepAlive,
			String status, String protocolType) {
		this.content = content;
		this.contentType = contentType;
		this.keepAlive = keepAlive;
		this.status = status;
		this.protocolType = protocolType;
		this.writeHeader = true;
	}

	@Override
	public byte[] toByteArray() {
		ByteArrayOutputStream baos = new ByteArrayOutputStream();
		try {
			if (this.writeHeader)
				writeHeader(baos);
			baos.write(this.content);
			baos.write(Toolbox.toUTF8Bytes("\r\n"));
		} catch (IOException e) {
			LOGGER.error("IO error writing to byte array", e);
		}
		return baos.toByteArray();
	}

	private void writeHeader(OutputStream out) throws IOException {
		StringBuilder sb = new StringBuilder();
		sb.append(this.protocolType + " " + this.status + "\r\n");
		sb.append("Content-Type: " + this.contentType + "\r\n");
		sb.append("Connection: " + (this.keepAlive ? "keep-alive" : "close")
				+ "\r\n");
		sb.append("\r\n");

		out.write(Toolbox.toUTF8Bytes(sb.toString()));
	}

	@Override
	public boolean endSession() {
		return !this.keepAlive;
	}

}
